cmake_minimum_required(VERSION 3.18)

project(protoc LANGUAGES CXX)

#查找对应的 Protobuf 配置文件方便后面进行链接

find_package(Protobuf 3.0 REQUIRED)

# 收集对应的proto文件打包：

file( GLOB  PROTO_FILES  ${CMAKE_CURRENT_SOURCE_DIR}/proto/*.proto)

set(PROTO_OUT_DIR ${CMAKE_CURRENT_BINARY_DIR}/pb)

# 不存在就创建对应目录：

file(MAKE_DIRECTORY ${PROTO_OUT_DIR} )


#建.pb.h与.pb.cc文件集合（可能proto目录里有多个.proto文件）：

set(PROTO_SRC "")
set(PROTO_HEAD "")

# 循环来根据proto生成对应c++文件：

foreach(PROTO ${PROTO_FILES})
 
# 获得基础文件名方便生成.pb.cc和.pb.h文件
 get_filename_component(BASE_NAME ${PROTO} NAME_WE)
  
 # 加入生成文件集合：
  list(APPEND PROTO_SRC ${PROTO_OUT_DIR}/${BASE_NAME}.pb.cc)
  list(APPEND PROTO_HEAD ${PROTO_OUT_DIR}/${BASE_NAME}.pb.h)

  # 执行脚本命令在对应位置生成对应文件：

  add_custom_command(
     OUTPUT "${PROTO_OUT_DIR}/${BASE_NAME}.pb.cc"  "${PROTO_OUT_DIR}/${BASE_NAME}.pb.h"
     COMMAND protoc
     ARGS --cpp_out=${PROTO_OUT_DIR} -I ${CMAKE_CURRENT_SOURCE_DIR}/proto/  ${PROTO}

     DEPENDS ${PROTO} 
     COMMENT "proto生成对应C++文件"
     VERBATIM # 一步步执行


  )

    
endforeach()

# 添加目标依赖；也就是make target的时候就会先生成对应依赖；实现依赖传递
add_custom_target(GET_PROTO_SOURCE DEPENDS ${PROTO_SRC}  ${PROTO_HEAD} )

# 上面循环完就完成了对应的.cc与.h文件集合收集；以及对应文件都放在pb目录。



# 进行对应.cc文件打包静态库

add_library(MYPROTO STATIC ${PROTO_SRC})
# 添加目标依赖；也就是make target的时候就会先生成对应依赖；实现依赖传递

add_dependencies(MYPROTO GET_PROTO_SOURCE )

# 使用库的时候去这里面找头文件
target_include_directories(MYPROTO INTERFACE ${PROTO_OUT_DIR})

target_link_libraries(MYPROTO PUBLIC protobuf::libprotobuf)

add_executable(main main.cpp)

target_link_libraries(main PRIVATE MYPROTO)

# 添加目标依赖；也就是make target的时候就会先生成对应依赖；实现依赖传递

add_dependencies( main  MYPROTO )





